//
//  SC_StackBarChartView.m
//  SCCharts
//
//  Created by Yang on 11/1/10.
//  Copyright 2010 __MyCompanyName__. All rights reserved.
//

#import "SC_StackBarChartView.h"


static float ChartTopMargin = 20.0f;
static float ChartBottomMargin = 100.0f;
static float ChartLeftMargin = 50.0f;
static float ChartRightMargin = 10.0f;

static int HighValue = 0;


@implementation SC_StackBarChartView
@synthesize delegate;

- (id)initWithFrame:(CGRect)frame {
    if ((self = [super initWithFrame:frame])) {
		dataArray = [[NSMutableArray alloc] init];
		viewWidth = frame.size.width;
		viewHeight = frame.size.height;
		[self setTouchEnabled:YES];
		self.backgroundColor = [UIColor whiteColor];
    }
    return self;
}
- (void)resetData:(NSArray *)array {
	
	[dataArray setArray:array];
	[self calculateHighValue];
	[self setNeedsDisplay];
}
- (void)calculateHighValue {
	HighValue = 0;
	for (SC_StackBarChartData *data in dataArray) {
		if ((data.over + data.normal + data.closed) > HighValue) {
			HighValue = data.over + data.normal + data.closed;
		}
	}
	HighValue += HighValue * 0.1;
	if (HighValue % 25 != 0) {
		//HighValue = ((HighValue / 5 / 10) + 1) * 10 * 5;
		HighValue = ((HighValue / 25) + 1) * 25;
	}
}

// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect {
	CGContextRef context = UIGraphicsGetCurrentContext();
	[self drawBackLines:context];
	[self drawYAxisLabels:context];
	[self drawStackBars:context];
	[self drawTitles:context];
	[self drawComments:context];
}
- (void)drawBackLines:(CGContextRef )context {
	CGContextSetStrokeColorWithColor(context,[SC_StackBarChartColors backgroundLineColor].CGColor);
	CGContextSetLineWidth(context, 1.0f);
	CGContextSetLineCap(context, kCGLineCapRound);
	CGContextSetLineJoin(context, kCGLineJoinRound);
	CGContextSetAllowsAntialiasing(context, NO);
	float width = viewWidth - ChartRightMargin - ChartLeftMargin;
	float height = viewHeight - ChartTopMargin - ChartBottomMargin;
	NSInteger total = [dataArray count];
	// 画横线
	for (int i = 0; i < 6 ; i++) {
		CGContextMoveToPoint(context, ChartLeftMargin, ChartTopMargin + i * (height / 5));
		CGContextAddLineToPoint(context,viewWidth - ChartRightMargin, ChartTopMargin + i * (height / 5));
	}
	// 画竖线
	for (int i = 0; i < total + 1; i++) {
		CGContextMoveToPoint(context, ChartLeftMargin + i * (width / total), ChartTopMargin);
		CGContextAddLineToPoint(context, ChartLeftMargin + i * (width / total), viewHeight - ChartBottomMargin);
	}
	CGContextStrokePath(context);
	CGContextSetAllowsAntialiasing(context, YES);
	
}
- (void)drawYAxisLabels:(CGContextRef )context {
	if (HighValue > 0) {
		int margin = HighValue / 5;
		float step = (viewHeight - ChartBottomMargin - ChartTopMargin) / 5.0f;
		for (int i = 0; i < 6; i ++) {
			NSString *string = [NSString stringWithFormat:@"%d", HighValue - i * margin];
			CGSize size = [string sizeWithFont:[UIFont systemFontOfSize:15.0f]];
			CGPoint point = CGPointMake(ChartLeftMargin - size.width - 5.0f, ChartTopMargin + i * step - size.height/2);
			[string drawAtPoint:point withFont:[UIFont systemFontOfSize:15.0f]];
			
		}
	}
}
- (void)drawStackBars:(CGContextRef )context {
	float width = viewWidth - ChartLeftMargin - ChartRightMargin;
	//float height = viewHeight - ChartTopMargin - ChartBottomMargin;
	float blockWidth = width / [dataArray count];
	float blockMargin = blockWidth * 0.15f;//10.0f; // 柱体之间的间距
	float yDeepHeight = 3.0f; // Y 轴方向上偏移的效果
	float frontWidth = (blockWidth - 2.0f * blockMargin) * 3.0f / 5.0f;
	float sideWidth = (blockWidth - 2.0f * blockMargin) * 2.0f / 5.0f;
    

	CGPoint points[4];
	int i = 0;
	for (SC_StackBarChartData *data in dataArray) {
		int total = 0;
		NSArray *lastColorArray=nil;
		// 正常
		if (data.normal > 0) {
			total += data.normal;
			CGContextSetStrokeColorWithColor(context, [UIColor greenColor].CGColor);
			NSArray *array = [SC_StackBarChartColors colorArrayForNormal];
			lastColorArray = array;
			//画正面
			UIColor *color = (UIColor *)[array objectAtIndex:0];
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total - data.normal]);
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total]);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.normal] + yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
			
			//画侧面
			color = (UIColor *)[array objectAtIndex:1];
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.normal] + yDeepHeight);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total - data.normal] - yDeepHeight);
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total] - yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
		}
		// 超标
		if (data.over > 0) {
			total += data.over;
			CGContextSetStrokeColorWithColor(context, [UIColor orangeColor].CGColor);
			NSArray *array = [SC_StackBarChartColors colorArrayForOver];
			lastColorArray = array;
			UIColor *color = (UIColor *)[array objectAtIndex:0];
			//画正面
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total - data.over]);
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total]);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.over] + yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
			
			//画侧面
			color = (UIColor *)[array objectAtIndex:1];
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.over] + yDeepHeight);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total - data.over] - yDeepHeight);
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total] - yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
		}
		// 故障和停产
		if (data.closed > 0) {
			total += data.closed;
			CGContextSetStrokeColorWithColor(context, [UIColor orangeColor].CGColor);
			NSArray *array = [SC_StackBarChartColors colorArrayForClosed];
			lastColorArray = array;
			UIColor *color = (UIColor *)[array objectAtIndex:0];
			//画正面
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total - data.closed]);
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total]);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.closed] + yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
			
			//画侧面
			color = (UIColor *)[array objectAtIndex:1];
			CGContextSetFillColorWithColor(context, color.CGColor);
			points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight );
			points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total - data.closed] + yDeepHeight);
			points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total - data.closed] - yDeepHeight);
			points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total] - yDeepHeight);
			
			CGContextAddLines(context, points, 4);
			CGContextDrawPath(context, kCGPathFill);
		}
		// 画顶部
        if (lastColorArray !=nil && [lastColorArray count]>2) {
            UIColor *color = (UIColor *)[lastColorArray objectAtIndex:2];
            CGContextSetFillColorWithColor(context, color.CGColor);
            points[0] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i, [self valueToY:total]);
            points[1] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth, [self valueToY:total] + yDeepHeight);
            points[2] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth + sideWidth, [self valueToY:total] - yDeepHeight );
            points[3] = CGPointMake(ChartLeftMargin + blockMargin + blockWidth * i + frontWidth - yDeepHeight, [self valueToY:total] - 2 * yDeepHeight);
            
            float x4 = ((points[3].y - points[0].y) * (points[2].x - points[1].x)) / (points[2].y - points[1].y) + points[0].x;
            points[3] = CGPointMake(x4, points[3].y);
            
            CGContextAddLines(context, points, 4);
            CGContextDrawPath(context, kCGPathFill);
        }
		
		i ++;
	}
	
}
- (float )valueToY:(int )value {
	float height = viewHeight - ChartTopMargin - ChartBottomMargin;
	float y = height / HighValue * value;
	return ChartTopMargin + (height - y);
}
- (void)drawTitles:(CGContextRef )context {
	if ([dataArray count]) {
		//CGContextSetStrokeColorWithColor(context, [UIColor blackColor].CGColor);
		CGContextSetFillColorWithColor(context, [UIColor blackColor].CGColor);
		float step = (viewWidth - ChartLeftMargin - ChartRightMargin) / [dataArray count];
		for (int i = 0; i < [dataArray count]; i ++) {
			
			SC_StackBarChartData *data = [dataArray objectAtIndex:i];
			NSString *string = data.title;
			CGSize size = [string sizeWithFont:[UIFont systemFontOfSize:16.0f]];
			CGPoint point = CGPointMake(ChartLeftMargin + step * i + step / 2 - size.width / 2, viewHeight - ChartBottomMargin + 10.0f);
			[string drawAtPoint:point withFont:[UIFont systemFontOfSize:16.0f]];
			
		}
	}
}
- (void)drawComments:(CGContextRef )context {
	float width = viewWidth - ChartLeftMargin - ChartRightMargin;
	float blockWidth = width / [dataArray count];
	float blockMargin = 10.0f;
	float yDeepHeight = 3.0f; // Y 轴方向上偏移的效果
	//float frontWidth = (blockWidth - 2.0f * blockMargin) * 3.0f / 5.0f;
    float frontWidth = (blockWidth - 2.0f * blockMargin) / 3.0f;
	//float sideWidth = (blockWidth - 2.0f * blockMargin) * 2.0f / 5.0f;
    float sideWidth = (blockWidth - 2.0f * blockMargin) / 3.0f;
	float margin = 70.0f;//图例和 图表的垂直距离
	float chartHeight = 12.0f;
    if (sideWidth >= 40) {
        sideWidth = 40;
        frontWidth = 40;
    }
    if (width > 240) {
        width = 240;
    }
    blockMargin = 8;
    if (blockWidth > 80) {
        blockWidth = 80;
    }
	CGPoint points[4];
	for (int i = 0; i < 3; i ++) {
		float started = viewWidth - ChartRightMargin - 50.0f - blockWidth * i;
		NSArray *array;
		NSString *string;
		if (i == 0) {
			array = [SC_StackBarChartColors colorArrayForNormal];
			string = @"正常";
		}
		else if (i == 1) {
			array = [SC_StackBarChartColors colorArrayForOver];
			string = @"超标";
		}
		else {
			array = [SC_StackBarChartColors colorArrayForClosed];
			string = @"离线";
		}
		// 正面
		UIColor *color = (UIColor *)[array objectAtIndex:0];
		CGContextSetFillColorWithColor(context, color.CGColor);
		points[0] = CGPointMake(started, viewHeight - ChartBottomMargin + margin);
		points[1] = CGPointMake(started + frontWidth, viewHeight - ChartBottomMargin + margin + yDeepHeight);
		points[2] = CGPointMake(started + frontWidth, viewHeight - ChartBottomMargin + margin + yDeepHeight - chartHeight);
		points[3] = CGPointMake(started, viewHeight - ChartBottomMargin + margin - chartHeight);
		CGContextAddLines(context, points, 4);
		CGContextDrawPath(context, kCGPathFill);
		// 侧面
		color = (UIColor *)[array objectAtIndex:1];
		CGContextSetFillColorWithColor(context, color.CGColor);
		points[0] = CGPointMake(started + frontWidth, viewHeight - ChartBottomMargin + margin + yDeepHeight);
		points[1] = CGPointMake(started + frontWidth, viewHeight - ChartBottomMargin + margin + yDeepHeight - chartHeight);
		points[2] = CGPointMake(started + frontWidth + sideWidth, viewHeight - ChartBottomMargin + margin  - chartHeight - yDeepHeight);
		points[3] = CGPointMake(started + frontWidth + sideWidth, viewHeight - ChartBottomMargin + margin - yDeepHeight);
		CGContextAddLines(context, points, 4);
		CGContextDrawPath(context, kCGPathFill);
		// 顶面
		color = (UIColor *)[array objectAtIndex:2];
		CGContextSetFillColorWithColor(context, color.CGColor);
		points[0] = CGPointMake(started , viewHeight - ChartBottomMargin + margin - chartHeight);
		points[1] = CGPointMake(started + frontWidth, viewHeight - ChartBottomMargin + margin - chartHeight + yDeepHeight);
		points[2] = CGPointMake(started + frontWidth + sideWidth, viewHeight - ChartBottomMargin + margin  - chartHeight - yDeepHeight);
		points[3] = CGPointMake(started + frontWidth + sideWidth, viewHeight - ChartBottomMargin + margin - chartHeight - 2.0f * yDeepHeight);
		float x4 = ((points[3].y - points[0].y) * (points[2].x - points[1].x)) / (points[2].y - points[1].y) + points[0].x;
		points[3] = CGPointMake(x4, points[3].y);
		CGContextAddLines(context, points, 4);
		CGContextDrawPath(context, kCGPathFill);
		
		CGContextSetFillColorWithColor(context, [UIColor blackColor].CGColor);
		CGSize size = [string sizeWithFont:[UIFont systemFontOfSize:15.0f]];
		CGPoint point = CGPointMake(started + blockWidth / 2 - size.width / 2 - 10.0f, viewHeight - ChartBottomMargin + margin + 10.0f);
		[string drawAtPoint:point withFont:[UIFont systemFontOfSize:15.0f]];
	}
	
	
}
- (void)setTouchEnabled:(BOOL )enabled {
	touchEnabled = enabled;
	//[self setNeedsDisplay];
	self.userInteractionEnabled = touchEnabled;
}
- (void)dealloc {
    [super dealloc];
}

#pragma mark Touch Events
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
}
- (void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event {
}
- (void) touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{
	if (touchEnabled) {
		UITouch *touch = [touches anyObject];
		CGPoint point = [touch locationInView:self];
		float width = viewWidth - ChartLeftMargin - ChartRightMargin;
		float height = viewHeight - ChartTopMargin - ChartBottomMargin;
		CGRect rect = CGRectMake(ChartLeftMargin, ChartTopMargin, width, height);
		if (CGRectContainsPoint(rect,point)) {
			float blockWidth = width / [dataArray count];
			NSInteger index = (point.x - ChartLeftMargin) / blockWidth;
			SC_StackBarChartData *data = [dataArray objectAtIndex:index];
			NSInteger total = data.normal + data.over + data.closed;
			float y = [self valueToY:total];
			if (point.y >= y) {
				[delegate stackBarIsTouchedAtIndex:index];
				//NSLog(@"selected at index %d",index);
			}
			
		}
	}
}
- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event {
}


@end
